package znet

import (
	"errors"
	"fmt"
	"sync"
	"zinx/Zinx/ziface"
)

// IConnManager接口实现, 定义一个ConnManager连接管理模块
type ConnManager struct {
	Connections map[uint32]ziface.IConnection // 连接集合
	ConnLock    sync.RWMutex                  // 保护连接集合的读写锁
}

// 初始化连接管理模块
func NewConnManager() *ConnManager {
	return &ConnManager{
		Connections: make(map[uint32]ziface.IConnection),
	}
}

// 添加连接
func (cm *ConnManager) AddConn(conn ziface.IConnection) {
	// 保护共享资源map, 写map时需要上写锁
	cm.ConnLock.Lock()
	defer cm.ConnLock.Unlock()
	// 添加连接
	cm.Connections[conn.GetConnID()] = conn
	fmt.Printf("[ConnManager]Add ConnID: %d,ConnLen: %d\n", conn.GetConnID(), cm.Len())
}

// 删除连接
func (cm *ConnManager) RemoveConn(conn ziface.IConnection) {
	// 保护共享资源map, 写map时需要上写锁
	cm.ConnLock.Lock()
	defer cm.ConnLock.Unlock()
	// 删除连接
	delete(cm.Connections, conn.GetConnID())
	fmt.Printf("[ConnManager]Remove ConnID: %d,ConnLen: %d\n", conn.GetConnID(), cm.Len())
}

// 返回指定ID对应的连接
func (cm *ConnManager) GetConn(connID uint32) (ziface.IConnection, error) {
	// 保护共享资源map, 读map时需要上读锁
	cm.ConnLock.RLock()
	defer cm.ConnLock.RUnlock()
	// 判断是否存在连接, 再获取连接
	if conn, ok := cm.Connections[connID]; ok {
		return conn, nil
	} else {
		return nil, errors.New(fmt.Sprintln("[ConnManager]Get fail, Conn not FOUND"))
	}
}

// 返回连接总数量
func (cm *ConnManager) Len() int {
	return len(cm.Connections)
}

// 停止并删除所有连接
func (cm *ConnManager) ClearConn() {
	// 保护共享资源map, 写map时需要上写锁
	cm.ConnLock.Lock()
	defer cm.ConnLock.Unlock()
	// 停止并删除所有连接
	for connID, conn := range cm.Connections {
		// 停止
		conn.Stop()
		// 删除
		delete(cm.Connections, connID)
	}
	fmt.Printf("[ConnManager]Clear All connection,ConnLen: %d\n", cm.Len())
}
